#ifndef BATTERY_ROPEENCODER_CAN_H
#define BATTERY_ROPEENCODER_CAN_H

#include "can/candevice.h"
#include "utility.h"
#include <QDebug>
#include <QObject>
#include <QThread>
#include <QTimer>
#include "ICANCmd.h"
#include <param.h>

#define NJLAKCAN     // UPDATE 选择can卡：  ZLGCAN NJLAKCAN

#ifdef NJLAKCAN
#include "can/njlikecandevice.h"
#define CAN_DEVICE_TYPE LCMiniPcie_432
#define CAN_DEVICE_RESULT_OK CAN_RESULT_OK
#define CAN_DEVICE_RESULT_ERROR CAN_RESULT_ERROR
#define CAN_NAME "NJLAK"
#endif

#ifdef ZLGCAN
#include "can/zlgcandevice.h"
#define CAN_DEVICE_TYPE VCI_USBCAN2
#define CAN_DEVICE_RESULT_OK STATUS_OK
#define CAN_DEVICE_RESULT_ERROR STATUS_ERR
#define CAN_NAME "ZLG"
#endif

/********** 电池与拉升编码器CAN2口 **********/
class Battery_Ropeencoder_can : public QObject
{
    Q_OBJECT
public:
    explicit Battery_Ropeencoder_can(DWORD dw_DeviceHandle, QObject *parent = nullptr);

    bool CanOpenAndStart();                            // 打开can设备
    bool CanStopAndClose();                            // 关闭can设备
    bool CanRecviveData();                             //处理can接收的数据
    void CanSendData(CanDataFrame* frames, ULONG i);   //处理can发送的数据
    void RegularGetData();                             //定期获取can数据
    void Start_Ropeencoder_Read( CanDataFrame &frame );           //开始读取拉绳编码器的值
    void Can_Set_Ropeencoder_Rate(CanDataFrame &frame );          //设置拉绳编码器反馈速率

/****************益佳通CAN通讯电池****************/
    enum ChargeState { Uncharge = 0, Charging = 1, Charged = 2 };
    Q_ENUM(ChargeState)

    //外部调用充电函数
    void charge(bool enable);  //电池开启充电

    struct BatteryData_YJT {
      double total_vol{0};                 //电池总电压
      double total_cur{0};                 //电池总电流
      double soc{0};                       //电池SOC
      double max_singel_vol{0};            //最高单体电压
      uint16_t max_singel_vol_num{0};      //最高单体电压串号
      double min_singel_vol{0};            //最低单体电压
      uint16_t min_singel_vol_num{0};      //最低单体电压串号
      int16_t max_temp{0};                 //电池最高温度
      uint16_t max_temp_num{0};            //电池最高温度编号
      int16_t min_temp{0};                 //电池最低温度
      uint16_t min_temp_num{0};            //电池最低温度编号
      bool charge_relay_state{false};      //电池充电继电器状态
      ChargeState charge_state{Uncharge};  //电池充电状态
    };

    struct Ropeencoder_Kubler{
        float  Ropeencoder_Height_Value{0}; //拉绳编码器反馈高度
    };

    BatteryData_YJT getBatteryData() const;

    Ropeencoder_Kubler GetRopeencoderData() const;

    Ropeencoder_Kubler Ropeencoder_data;

private:
    DWORD dw_Index = 0;   /* 第1个设备 */
    DWORD dw_Channel = 1; /* 第2个通道 */
    DWORD dw_DeviceHandle;
    BYTE dw_Btr0 = 0x03;  // BTR0   0014 -1M 0016-800K 001C-500K 011C-250K 031C-125K 041C-100K 091C-50K 181C-20K 311C-10K BFFF-5K
    BYTE dw_Btr1 = 0x1c;
    bool is_open_can = false; //CAN设备是否打开
    CanDevice* canDevice    =  nullptr;

    BYTE Ropeencoder_Rate[8] = {0x2B, 0x00, 0x18, 0x05, 0x64, 0x00, 0x00, 0x00};        // 拉绳编码器反馈速率 100MS

    BatteryData_YJT battery_data;

signals:
    void sigSendTips(const QString &);
    void sigShowCanData(const QByteArray &tips, const QString &string);
    void sigLoseConnect(const QString &);

public slots:
    void sltCanInit_1();
    void sltTimeOut();
};

#endif // BATTERY_ROPEENCODER_CAN_H


